package com.pri.chat.activity.vedio.widget;

import android.content.Context;
import android.net.ConnectivityManager;
import android.net.NetworkInfo;
import android.os.Handler;
import android.os.Looper;
import android.os.Message;

import java.io.File;
import java.io.FileOutputStream;
import java.io.InputStream;
import java.io.OutputStream;
import java.net.HttpURLConnection;
import java.net.URL;
import java.util.LinkedList;
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;
import java.util.concurrent.Semaphore;

/**
 * 说明：图片加载类
 * 作者：易涛
 * 时间：2016-4-14
 */
public class FileDownLoadUtil {
	private Context mContext;
	/**
	 * imageLoader对象，实现单例模式
	 */
	private static FileDownLoadUtil mInstance;
	/**
	 * 加载网络图片缓存的地址
	 */
	private String NET_IMAGE_CACHE_PATH = null;
	/**
	 * 线程池
	 */
	private ExecutorService mThreadPool;
	/**
	 * 默认线程数
	 */
	private static final int DEAFULT_THREAD_COUNT = 5;
	/**
	 * 队列的调度方式
	 */
	private Type mType = Type.LIFO;

	/**
	 * 任务队列
	 */
	private LinkedList<Runnable> mTaskQueue;
	/**
	 * 后台轮询线程
	 */
	private Thread mPoolThread;
	private Handler mPoolThreadHandler;
	/**
	 * 信号量
	 */
	private Semaphore mSemaphorePoolThreadHandler = new Semaphore(0);
	private Semaphore mSemaphoreThreadPool;
	/**
	 * 说明：枚举类型
	 * 作者：易涛
	 * 时间：2016-4-14
	 */
	public enum Type {
		FIFO, LIFO
	}

	/**
	 * 说明： 初始化数据
	 * @param threadCount 线程数
	 * @param type
	 *            加载机制：1.FIFO先进先出; 2.LIFO后进先出
	 * @param cache_path
	 *            缓存地址 作者：易涛 时间：2016-4-14
	 */
	public void init(Context context, int threadCount, Type type, String cache_path) {
		this.mContext = context;
		this.mType = type;
		this.NET_IMAGE_CACHE_PATH = cache_path;
		// 后台轮询线程
		mPoolThread = new Thread() {
			@Override
			public void run() {
				Looper.prepare();
				mPoolThreadHandler = new Handler() {
					@Override
					public void handleMessage(Message msg) {
						// 线程池去去除一个任务进行执行
						Runnable task = getTask();
						if (task != null) {
							mThreadPool.execute(task);
							try {
								mSemaphoreThreadPool.acquire();
							} catch (InterruptedException e) {
								e.printStackTrace();
							}
						}
					}
				};
				// 释放一个信号量
				mSemaphorePoolThreadHandler.release();
				Looper.loop();
			}
		};
		mPoolThread.start();
		// 创建线程池
		mThreadPool = Executors.newFixedThreadPool(threadCount);
		mTaskQueue = new LinkedList<Runnable>();
		mSemaphoreThreadPool = new Semaphore(threadCount);
	}

	public static FileDownLoadUtil getInstance() {
		if (mInstance == null) {
			synchronized (FileDownLoadUtil.class) {
				if (mInstance == null) {
					mInstance = new FileDownLoadUtil();
				}
			}
		}
		return mInstance;
	}

	/**
	 * 说明：根据path给imageView设置图片
	 * 作者：易涛
	 * 时间：2016-4-14
	 */
	public void downLoadFile(final String path) {
			addTask(new Runnable() {
				@Override
				public void run() {
					String finishPath = NET_IMAGE_CACHE_PATH + path.substring(path.lastIndexOf("/") + 1).replace("mp4","");
                    String filePath = NET_IMAGE_CACHE_PATH + path.substring(path.lastIndexOf("/") + 1).replace("mp4","")+"download";
                    downLoadFile(path,filePath,finishPath);
					mSemaphoreThreadPool.release();
				}
			});

	}

	/**
	 * 说明：下载图片
	 * 作者：易涛
	 * 时间：2016-4-14
	 */
	public void downLoadFile(String path, String filePath, String finishPath) {
		boolean downLoadSuccess = true;
		try {
			File fileDir = new File(NET_IMAGE_CACHE_PATH);
			if (!fileDir.exists()) {
				fileDir.mkdirs();
			}
			// 准备拼接新的文件名（保存在存储卡后的文件名）
			File file = new File(filePath);
			// 如果文件不存在
			if (!file.exists()) {
				file.createNewFile();
			}
			// 下载文件的开始位置
			int startPosition = (int) file.length();
			URL myFileURL = new URL(path);
			// 获得连接
			HttpURLConnection conn = (HttpURLConnection) myFileURL.openConnection();
			// 设置超时时间为6000毫秒，conn.setConnectionTiem(0);表示没有时间限制
			conn.setConnectTimeout(10000);
			// 连接设置获得数据流
			conn.setDoInput(true);
			// 不使用缓存
			conn.setUseCaches(false);
			// 得到数据流
			InputStream is = conn.getInputStream();
			OutputStream out = new FileOutputStream(file);
			byte[] buffer = new byte[1024*1024];
			int len = 0;
			// 代表当前读到的服务器数据的位置 ,同时这个值已经存储的文件的位置
			while (true) {
				// 判断有网络时才执行
				if (isNetConnect()) {
					len = is.read(buffer);
					if (len != -1) {
						// 向目标文件中写入数据
						out.write(buffer, 0, len);
					} else {
						downLoadSuccess = true;
						file.renameTo(new File(finishPath));
						break;
					}
				} else {
					downLoadSuccess = false;
					break;
				}
			}
			// 关闭数据流
			is.close();
			out.close();
		} catch (Exception e) {
			downLoadSuccess = false;
			e.printStackTrace();
		} finally {
			if (!downLoadSuccess) {
				File file = new File(filePath);
				if (file.exists()) {
					file.delete();
				}
			}
		}

	}

	/**
	 * 说明：获取网络状态
	 * 作者：易涛
	 * 时间：2016-4-15
	 */
	protected boolean isNetConnect() {
		try {
			ConnectivityManager _ConnectivityMabager = (ConnectivityManager) mContext.getSystemService(Context.CONNECTIVITY_SERVICE);
			NetworkInfo _NetworkInfo = _ConnectivityMabager.getActiveNetworkInfo();
			return _NetworkInfo.isConnected();
		} catch (Exception e) {
			return false;
		}
	}


	/**
	 * 说明：得到要执行的任务
	 * 作者：易涛
	 * 时间：2016-4-15
	 */
	private Runnable getTask() {
		if (mType == Type.FIFO) {
			return mTaskQueue.removeFirst();
		} else if (mType == Type.LIFO) {
			if (mTaskQueue != null && mTaskQueue.size() > 0) {
				return mTaskQueue.removeLast();
			}
		}
		return null;
	}

	/**
	 * 说明：添加任务
	 * 作者：易涛
	 * 时间：2016-4-15
	 */
	private void addTask(Runnable runnable) {
		mTaskQueue.add(runnable);
		try {
			if (mPoolThreadHandler == null) {
				mSemaphorePoolThreadHandler.acquire();// 相当于等一会
			}
		} catch (InterruptedException e) {
			e.printStackTrace();
		}
		mPoolThreadHandler.sendEmptyMessage(0x110);
	}
}
